﻿using System.Linq;
using System.Threading;
using CommonLibrary;
using CommonLibrary.ConfigurationManager;
using CommonLibrary.Helpers;
using CommonLibrary.Models.Configurations;
using CommonLibrary.Models.ControllerStates;
using CommonLibrary.Models.ControllerStates.PS3;
using CommonLibrary.Models.General;
using CommonLibrary.Models.Profiles;

namespace SmartController
{
    public class AppContext : ViewModel, IAppContext
    {
        #region Props
        private static Config _appConfig;
        public Config GlobalConfig
        {
            get { return _appConfig ?? (_appConfig = new Config()); }
            private set { _appConfig = value; }
        }

        #region Controller States
        // TODO add support for multiple Controler States
        private static ControllerState _state;
        public ControllerState ControllerState
        {
            get { return _state ?? (_state = new PS3ControllerState()); }
            private set { _state = value; OnPropertyChanged("ControllerState"); }
        }

        private static GeneralInformation _generalInformation;
        public GeneralInformation GeneralInfo
        {
            get { return _generalInformation ?? (_generalInformation = new GeneralInformation()); }
        }
        #endregion

        #region Application Profiles and Configs
        private static ProcessedProfile _processedProfile;
        public ProcessedProfile ProcessedProfile
        {
            get { return _processedProfile ?? (_processedProfile = new ProcessedProfile()); }
            set { _processedProfile = value; }
        }

        private static ProfileConfig _profileConfig;
        public ProfileConfig ProfileConfig
        {
            get { return _profileConfig ?? (_profileConfig = new ProfileConfig()); }
            private set { _profileConfig = value; OnPropertyChanged("ProfileConfig"); }
        }
        #endregion
        #endregion

        #region Initialize procedures
        private static AppContext _instance;
        private static readonly Mutex Mux = new Mutex();

        public static AppContext Current
        {
            get
            {
                Mux.WaitOne();

                if (_instance == null)
                    _instance = new AppContext();


                Mux.ReleaseMutex();

                return _instance;
            }
        }
        #endregion

        #region Constructor
        private AppContext()
        {
            GlobalConfig = GlobalConfig.GetConfig();
        }
        #endregion

        #region Methods
        public void GetApplicationProfile(string applicationName, int configId = -1)
        {
            if (!string.IsNullOrWhiteSpace(applicationName) && ProcessedProfile.ProfileName != applicationName)
                ProcessedProfile.GetApplicationProfile(applicationName);

            if (configId != -1)
                ProfileConfig = ProcessedProfile.Configs.FirstOrDefault(c => c.Id == configId);
        }
        #endregion
    }
}
